2023/12/234090字符

纯函数

  • 不依赖,修改作用域之外变量的函数(纯净度)。避免产生 bug
    • 不能以任何形式改动参数;
    • 不可以有异步;
    • 不可以对环境外部环境中的数据造成影响。
var arr = [{name : 'wang'}];

function add (arr) {
    var obj = {name : 'bz'};
    var newArr = [];
    for (var i = 0; i < _arr.length; i ++) {
        newArr[i] = deepClone(_arr[i]);  // 克隆下原始数据,避免更改 arr[0].name = 'dddd'
    }
    newArr.push(obj);  // 这里不能 push 给 arr,改变了原始数据将不再是纯函数
    return newArr;
}
var newArr = add(arr);
newArr.push({name : 'hehe'});
// newArr --> {name: 'wang', name: 'bz', name: 'hehe'}

函数记忆

function factorial (n) {
    if(n == 0 || n ==1){
        return 1;
    }else{
        return n * factorial(n - 1);
    }
}

function memorize (fn) {
    var cache = {};
    return function(){
        var key = arguments.length + Array.prototype.join.call(arguments);
        if(cache[key]){
            return cache[key];
        }else{
            cache[key] = fn.apply(this, arguments);
            return cache[key];
        }
    }
}

var newF = memorize(factorial);

console.time('no M');
console.log(factorial(5));  //--> 120
console.timeEnd('no M');
console.time('fir M');
console.log(factorial(5));  //--> 120
console.timeEnd('fir M');
console.time('sec M');
console.log(factorial(5));  //--> 120
console.timeEnd('sec M');

柯理化

function FixedParmasCuury (fn) {
    let _arg = [].slice.call(arguments, 1);
    return function () {
        let newArg = _arg.concat( [].slice.call(arguments, 0) );
        return fn.apply(this, newArg);
    }
}

function Curry (fn, len) {
    let length = len || fn.length;  // 
    return function () {
        if (arguments.length < length) {
            let combined = [fn].concat( [].slice.call(arguments, 0) );
            return Curry(FixedParmasCuury.apply(this, combined), length - arguments.length);
        } else {
            return fn.apply(this, arguments)
        }
    }
}
  • 柯理化求和
function sum() {
    var arr = [].slice.apply(arguments);
    var fn = function(){
        arr = arr.concat([].slice.apply(arguments))
        return fn;
    }
    fn.sumOf = function(){
        return  arr.reduce((total,num)=>total+num,0);
    }
    return fn;
}

sum(1,3).sumOf();  //--> 4
sum(1,3)(2,4).sumOf();  //--> 10

节流与防抖

  • 节流:减少执行频率(页面滚动、窗口调整,抢购疯狂点击)
<div class="show">0</div>
<button class="btn" value="button">click</button>

<script>
    var oDiv = document.getElementsByClassName('show')[0];
    var oBtn = document.getElementsByClassName('btn')[0];

    // 节流指减少执行频率
    // 防抖是多次执行后,只执行一次
    function throttle(handler, wait){
        var lastTime = 0;
        return function(e){
            var nowTime = new Date().getTime();
            if (nowTime - lastTime > wait) {
                handler.apply(this, arguments);
                lastTime = nowTime;
            }
        }
    }

    function buy(e){
        console.log(this, e);
        oDiv.innerHTML = parseInt(oDiv.innerHTML) + 1;
    }

    oBtn.onclick = throttle(buy, 1000);
</script>
  • 防抖:多次执行后,只执行一次(实时搜索,拖拽)
<input type="text" class="inp">

<script>
    var inp = document.getElementsByClassName('inp')[0];
    var timer = null;
    
    function debounce(handler, delay){
        return function(){
            var _self = this, _arg = arguments;
            clearTimeout(timer);
            timer = setTimeout(function(){
                handler.apply(_self, _arg);
            }, delay);
        }
    }
    function ajax(e){
        console.log(e, this.value);
    }

    inp.onclick = debounce(ajax, 2000);
</script>